<template>
  <el-dialog
    :title="title"
    :visible.sync="myVisible"
    size=""
    @close="handleClose"
    center>
    <div class="cropper">
      <el-row :gutter="20">
        <el-col :span="preview ? span[0] : 24" class="cropper-content">
          <img src="src" />
        </el-col>
        <el-col v-if="preview && preview.length" :span="span[1]" class="cropper-preview">
          <div v-for="(item, index) in preview" :key="index">
            <h4>图片预览</h4>
            {{preview.length === 1? '' : item}}
            <br/>
            <img :src="cropImage" :style="`width: ${item.split('x')[0]}px;height: ${item.split('x')[1]}px;`" />
          </div>  
        </el-col>
      </el-row>
    </div>
    <div slot="footer">
      <el-button type="primary" @click="handleSubmit" :disabled="!cropImage">确定</el-button>
      <el-button v-if="$listeners.upload" @click="handleUpload" >重新上传</el-button>
      <el-button @click="handleClose">取消</el-button>
    </div>
  </el-dialog>
</template>

<script>
  import Vue from 'vue'
  export default {
    componentName: 'ECropper',
    props: {
      options: {
        type: Object
      },
      src: {
        type: String
      },
      visible: {
        type: Boolean,
        default: false
      },
      preview: {
        type: Array,
        default () {
          return ['100x100']
        }
      },
      title: {
        type: String,
        default: '图片裁剪'
      },
      span: {
        type: Array,
        default () {
          return [18, 6]
        }
      }
    },
    data () {
      return {
        myVisible: this.visible,
        cropImage: ''
      }
    },
    watch: {
      src (value) {
        this.$$vm.src = value
        this.$$vm.$refs.cropper.replace(value)
      },
      visible (value) {
        this.myVisible = value
        value && !this.$$vm && this.$nextTick(this.init)
      }
    },
    mounted () {
      this.visible && this.$nextTick(this.init)
    },
    destroyed () {
      this.$el && this.$el.parentNode && this.$el.parentNode.removeChild(this.$el)
    },
    methods: {
      handleCropImage () {
        if (this.$$vm && this.$$vm.$refs.cropper) {
          this.cropImage = this.$$vm.$refs.cropper.getCroppedCanvas().toDataURL()
        }
      },
      handleClose () {
        this.$emit('close').$emit('update:visible', false)
      },
      handleSubmit () {
        this.$emit('submit', this.cropImage).$emit('update:visible', false)
      },
      handleUpload () {
        this.$emit('upload')
      },
      init () {
        let self = this
        let VueCropper = require('vue-cropperjs')
        let node = this.$el.querySelector('.cropper-content img')
        let defaultOptions = {
          aspectRatio: 1,
          guides: true,
          viewMode: 1,
          dragMode: 'crop',
          autoCrop: true,
          autoCropArea: 0.5,
          minContainerWidth: 250,
          minContainerHeight: 250,
          minCropBoxWidth: 100,
          minCropBoxHeight: 100,
          rotatable: false,
          movable: true,
          background: true,
          imgStyle: {
            width: node.parentNode.offsetWidth + 'px',
            height: 460 + 'px'
          },
          ready: self.handleCropImage,
          cropmove: self.handleCropImage,
          zoom: self.handleCropImage
        }
        this.$$vm = new Vue({
          el: node,
          data () {
            return {
              src: self.src
            }
          },
          render (createElement) {
            return createElement(VueCropper.default, {
              props: {
                ...defaultOptions,
                ...self.options,
                src: this.src
              },
              ref: 'cropper'
            })
          }
        })
      }
    }
  }
</script>
